const GLib    = imports.gi.GLib;
const Lang    = imports.lang;
const Mx      = imports.gi.Mx;
const Octopus = imports.gi.Octopus;
const Signals  = imports.signals;

const AlbumArt = imports.albumArt;

const ICONSIZE = 30;

function ControlPanel(container) {
	this._init(container);
}

ControlPanel.prototype = {
	_init: function (container) {
		this.controlPanelStack = new Mx.Stack ({ name: 'controlPanel-background' });
		container.add_child (this.controlPanelStack);

		this.controlLayout = new Mx.BoxLayout ({ orientation: Mx.Orientation.HORIZONTAL });
		this.controlPanelStack.add_child (this.controlLayout);

		this.albumArtStack = new Mx.Stack ({ style_class: 'controlPanel-album-background' });
		this.controlLayout.add_child (this.albumArtStack);
		this.albumArt = new AlbumArt.AlbumArt (this.albumArtStack,
		                                       150); //albumArtSize
		this.albumArtOverlay = new Mx.Frame ({ style_class: 'controlPanel-album-overlay' });
		this.albumArtStack.add_child (this.albumArtOverlay);

		this.controlVerticalBox = new Mx.BoxLayout ({ style_class: 'controlPanel-layout',
		                                              orientation: Mx.Orientation.VERTICAL });
		this.controlLayout.add_child (this.controlVerticalBox);

		//playtime, duration
		this.controlPlaytimeDurationHBox = new Mx.BoxLayout ({ orientation: Mx.Orientation.HORIZONTAL,
		                                                       spacing: 10 });
		this.controlVerticalBox.add_child (this.controlPlaytimeDurationHBox);

		this.controlPlaytimeStack = new Mx.Stack ();
		this.controlPlaytimeDurationHBox.add_child (this.controlPlaytimeStack);
		this.controlPlaytimeProgressbar = new Mx.ProgressBar ({ style_class: 'controlPanel-playtime-progressbar',
		                                                        width: 450 });
		this.controlPlaytimeStack.add_child (this.controlPlaytimeProgressbar);
		this.controlPlaytimeSlider = new Mx.Slider ({ style_class: 'controlPanel-playtime-slider',
		                                              width: 450,
		                                              reactive: true });
		this.controlPlaytimeStack.add_child (this.controlPlaytimeSlider);
		this.controlPlaytimeSlider.connect ('notify::value', Lang.bind (this, function () {
			this.controlPlaytimeSeekLabel.text = Octopus.utils_format_duration(this._duration*this.controlPlaytimeSlider.value);
		}));
		this.controlPlaytimeSlider.connect ('slide-stop', Lang.bind(this, function () {
			global.get_playback ().xmms_seek (this._duration * this.controlPlaytimeSlider.value);
			this.controlPlaytimeSeekLabel.text = "";
		}));
		this.controlPlaytimeSlider.connect ('enter-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "seek");
		}));
		this.controlPlaytimeSlider.connect ('leave-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "");
		}));
		this.controlPlaytimeSeekLabel = new Mx.Label ({ style_class:'controlPanel-playtime-seek-label' });
		this.controlPlaytimeStack.add_child (this.controlPlaytimeSeekLabel);
		global.get_playback ().connect ('playback_playtime', Lang.bind(this, function (control_model, pos) {
			if (control_model.duration != 0) {
				let val = (pos / control_model.duration);
				if (val > 1) val = 1;
				this.controlPlaytimeProgressbar.progress = val;
			} else {
				this.controlPlaytimeProgressbar.progress = 0;
			}
		}));

		this.controlDuration = new Mx.Label ({ style_class: 'controlPanel-duration',
		                                       text: "0:00" });
		this.controlPlaytimeDurationHBox.add_child (this.controlDuration);
		//play/pause, stop, prev, next, volume
		this.controlCommandHBox = new Mx.BoxLayout ({ style_class: 'controlPanel-command-layout',
		                                              orientation: Mx.Orientation.HORIZONTAL,
		                                              height: ICONSIZE });
		this.controlVerticalBox.add_child (this.controlCommandHBox);
		this.controlPlayPause = new Mx.Button ({ style_class: 'controlPanel-play-pause',
		                                         width: ICONSIZE,
		                                         is_toggle: true });
		this.controlCommandHBox.add_child (this.controlPlayPause);
		this.controlPlayPause.connect ('clicked', Lang.bind(this, function () {
			if (this.controlPlayPause.toggled) {
				global.get_playback ().xmms_play ();
			} else {
				global.get_playback ().xmms_pause ();
			}
		}));
		this.controlPlayPause.connect ('enter-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "play/pause");
		}));
		this.controlPlayPause.connect ('leave-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "");
		}));
		this.controlStop = new Mx.Button ({ style_class: 'controlPanel-stop',
		                                    width: ICONSIZE });
		this.controlCommandHBox.add_child (this.controlStop);
		this.controlStop.connect ('clicked', Lang.bind(this, function () {
			global.get_playback ().xmms_stop ();
		}));
		this.controlStop.connect ('enter-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "stop");
		}));
		this.controlStop.connect ('leave-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "");
		}));
		this.controlPrev = new Mx.Button ({ style_class: 'controlPanel-prev',
		                                    width: ICONSIZE });
		this.controlCommandHBox.add_child (this.controlPrev);
		this.controlPrev.connect ('clicked', Lang.bind(this, function () {
			global.get_playback ().xmms_set_prev ();
		}));
		this.controlPrev.connect ('enter-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "previous");
		}));
		this.controlPrev.connect ('leave-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "");
		}));
		this.controlNext = new Mx.Button ({ style_class: 'controlPanel-next',
		                                    width: ICONSIZE });
		this.controlCommandHBox.add_child (this.controlNext);
		this.controlNext.connect ('clicked', Lang.bind(this, function () {
			global.get_playback ().xmms_set_next ();
		}));
		this.controlNext.connect ('enter-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "next");
		}));
		this.controlNext.connect ('leave-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "");
		}));
		this.controlSeparator = new Mx.Frame ({ style_class: 'controlPanel-command-separator',
		                                        width: 20 });
		this.controlCommandHBox.add_child (this.controlSeparator);
		this.controlVolumeIcon = new Mx.Icon ({ style_class: 'controlPanel-volume-icon',
		                                        width: ICONSIZE });
		this.controlCommandHBox.add_child (this.controlVolumeIcon);
		this.controlVolumeSlider = new Mx.Slider ({ style_class: 'controlPanel-volume-slider',
		                                            width: 250,
		                                            reactive: true });
		this.controlCommandHBox.add_child (this.controlVolumeSlider);
		this.controlVolumeSlider.connect ('slide-start', Lang.bind(this, function () {
			this.slideStartTime = GLib.get_monotonic_time ();
		}));
		this.controlVolumeSlider.connect ('slide-stop', Lang.bind(this, function () {
			global.get_playback ().xmms_apply_volume (this.controlVolumeSlider.value * 100);
		}));
		this.controlVolumeSlider.connect ('notify::value', Lang.bind (this, function () {
			let now = GLib.get_monotonic_time ();
			if ((now - this.slideStartTime) > 250 * 1000) { //250msec = 250 * 1000 usec
				this.slideStartTime = GLib.get_monotonic_time ();
				global.get_playback ().xmms_apply_volume (this.controlVolumeSlider.value * 100);
			}
		}));
		this.controlVolumeSlider.connect ('enter-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "volume");
		}));
		this.controlVolumeSlider.connect ('leave-event', Lang.bind(this, function () {
			this.emit ('show-message-bar-text', "");
		}));
		//info (title, artist)
		this.controlTitle = new Mx.Label ({ style_class: 'controlPanel-title' });
		this.controlVerticalBox.add_child (this.controlTitle);
		this.controlArtist = new Mx.Label ({ style_class: 'controlPanel-artist' });
		this.controlVerticalBox.add_child (this.controlArtist);

		this.controlPanelOverlay = new Mx.Frame ({ name: 'controlPanel-overlay' });
		this.controlPanelStack.add_child (this.controlPanelOverlay);

		global.get_playback ().connect ('medialib_info_changed', Lang.bind (this, this.on_medialib_info_changed));
		global.get_playback ().connect ('playback_status_stop', Lang.bind(this, function (/*Playback*/ playback_model) {
			this.controlPlayPause.toggled = false;
			this.controlPlaytimeProgressbar.progress = 0;
		}));
		global.get_playback ().connect ('playback_status_play', Lang.bind(this, function (/*Playback*/ playback_model) {
			this.controlPlayPause.toggled = true;
		}));
		global.get_playback ().connect ('playback_status_pause', Lang.bind(this, function (/*Playback*/ playback_model) {
			this.controlPlayPause.toggled = false;
		}));
		global.get_playback ().connect ('playback_volume', Lang.bind(this, function (/*Playback*/ playback_model,/*int*/ volume) {
			this.controlVolumeSlider.value = (volume / 100);
		}));
		global.get_playback ().load_playback ();
	},

	on_medialib_info_changed: function (/*Playback*/ playback_model) {
		this.albumArt.loadAlbumArt (playback_model.picture_front);
		this.controlTitle.text    = playback_model.title;
		this._duration            = playback_model.duration;
		this.controlDuration.text = Octopus.utils_format_duration (playback_model.duration);
		this.controlArtist.text   = playback_model.artist;
		this.albumArt.defaultAlbumArtArtist.text = playback_model.artist;
		this.albumArt.defaultAlbumArtAlbum.text  = playback_model.album;
	}
};

Signals.addSignalMethods(ControlPanel.prototype);
